﻿using AutoMapper;
using BCGM.MedicalWisdom.Common.AliYun;
using BCGM.MedicalWisdom.Common.AppConfig;
using BCGM.MedicalWisdom.Common.Helper;
using BCGM.MedicalWisdom.IServices;
using BCGM.MedicalWisdom.Model;
using BCGM.MedicalWisdom.Model.DTO;
using BCGM.MedicalWisdom.Model.Models;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.IdentityModel.Tokens;
using Snowflake.Core;
using System.IdentityModel.Tokens.Jwt;
using System.Linq.Expressions;
using System.Security.Claims;
using System.Text;
using BCGM.MedicalWisdom.Model.BCGM_PatientModel;
using StackExchange.Redis;
using BCGM.MedicalWisdom.Extensions;
using Aop.Api.Request;
using System;
using SqlSugar.Extensions;
using Microsoft.EntityFrameworkCore.Metadata.Internal;

namespace BCGM.MedicalWisdom.Api.Controllers
{

    /// <summary>
    /// 患者用户表（登录、注册）
    /// </summary>
    //[Produces("application/json")]
    [Route("api/[controller]/[action]")]
    //[AllowAnonymous]
    [ApiController]
    //[Authorize(Permissions.Name)]
    public class PatientUserController : ControllerBase
    {
        /// <summary>
        /// 服务器接口，因为是模板生成，所以首字母是大写的，自己可以重构下
        /// </summary>
        private readonly IPatientUserServices _patientUserServices;
     
        private ISession MySession => HttpContext.Session;
        private readonly IRedisBasketRepository _redisBasketRepository;

        public PatientUserController(IPatientUserServices patientUserServices, IRedisBasketRepository redisBasketRepository)
        {
            _patientUserServices = patientUserServices;
            _redisBasketRepository = redisBasketRepository;
        }
        //private RedisTemplate redisTemplate;

        //private static HttpContext.Session.SetString("userLoginPhone", code);

        //static CSRedis.CSRedisClient redis = new CSRedis.CSRedisClient("127.0.0.1:6379");
        /// <summary>
        /// 获取验证码
        /// </summary>
        /// <param name="phone"></param>
        [HttpGet]
        [AllowAnonymous]
        public async Task GetCode(string phone)
        {
            Random random = new Random();
            string yz =random.Next(111111,999999).ToString();
            //给key值赋值
            string key = phone;
          
            if (phone.Length == 11)
            {

                //string hasKey = redisTemplate.hasKey(key);
                //判断redis里是否存在该手机号
                var qwe =await _redisBasketRepository.Exist(key);
                //为false 
                if (qwe == true)
                {
                    return;
                }
                else
                {
                    //设置过期时间
                   // TimeSpan ts = new TimeSpan(0,5,0);//timeSpanz转换成(天，分，秒)
                    //通过阿里云发送验证码
                    AliSendSms.send(phone, yz);
                    //存入redis
                    await _redisBasketRepository.Set(key, yz, TimeSpan.FromSeconds(300));
                }
            }
        }

        /// <summary>
        /// 用户注册
        /// </summary>
        /// <param name="input"></param>
        [HttpPost]
        public async Task<MessageModel<string>> UserAdds(PatientUserAddDTO input)
        {
            var data = new MessageModel<string>();
            //从redis获取到缓存的验证码
            string ph =await _redisBasketRepository.Get<string>(input.Phone);

            //从前端页面获取到的手机验证码
            //string codemsg = MySession.GetString("userLoginPhone");
            //if (userLogin.Code != codemsg)
            //{
            //    data.success = false;
            //    data.msg = "验证码错误！";
            //    return data;
            //}
            if (ph!=input.Code)
            {
                data.success = false;
                data.msg = "验证码错误！";
                return data;
            }
            var counts = await _patientUserServices.Query(d => d.Phone == input.Phone);
            if (counts.Count() > 0)
            {
                data.msg = "该手机号已经注册";
                return data;
            }

            //添加此数据，返回受影响行数
            var id = await _patientUserServices.UserAdds(input);
            data.success = id > 0;
            if (data.success)
            {
                data.response = id.ObjToString();
                data.msg = "添加成功";
            }

            return data;
        }

        /// <summary>
        /// 患者登录
        /// </summary>
        /// <param name="patientLoginDTO"></param>
        /// <returns></returns>
        [HttpPost]
        //[Route("Token")]
        public async Task<MessageModel<string>> PatientLogging(PatientLoginDTO patientLoginDTO)
        {
            var qwe = MD5Helper.MD5Encrypt16(patientLoginDTO.LoginPassword);
            LoginUserInfo loginUserInfo = new LoginUserInfo();
            string jwtStr = string.Empty;
            bool suc = false;
            if (patientLoginDTO.LoginName.IsNotEmptyOrNull() && patientLoginDTO.LoginPassword.IsNotEmptyOrNull())
            {
                var user = (await _patientUserServices.Query(s => s.Phone == patientLoginDTO.LoginName && s.Pwd == qwe && s.IsDeleted == false)).FirstOrDefault();
                if (user != null)
                {
                    //荷载信息
                    List<Claim> claims = new List<Claim>()
                    {
                        new Claim(ClaimTypes.Name,user.Phone),
                        new Claim(ClaimTypes.NameIdentifier,user.PatientUserId.ToString())
                    };

                    //string refreshToken = Guid.NewGuid().ToString();
                    //RedisHelper.Initialization(redis);
                    //redis.HSet("loginToken", refreshToken, JsonConvert.SerializeObject(user));
                    //redis.Expire(refreshToken, 3000);

                    ////签名秘钥
                    string secret = AppSecretConfig.Audience_Secret_String;
                    var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(secret));
                    ////对秘钥加密
                    var credentials = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);

                    //过期时间
                    DateTime expires = DateTime.Now.AddSeconds(2 * 3600);   //两小时

                    //实例化JWT安全令牌对象
                    var jwtToken = new JwtSecurityToken(
                        issuer: "YYF",           //发布者
                        audience: "everyone",    //受众
                        claims: claims,          //发起人 订阅者
                        expires: expires,        //过期时间
                        signingCredentials: credentials  //秘钥
                        );

                    //序列化jwt令牌  从而得到一个字符串
                    jwtStr = new JwtSecurityTokenHandler().WriteToken(jwtToken);
                    suc = true;
                    loginUserInfo.Login_name = user.UserName;
                    loginUserInfo.User_img = user.Image;
                }
                else
                {
                    jwtStr = "login fail!!!";
                }
            }


            return new MessageModel<string>()
            {
                data = loginUserInfo,
                success = suc,
                msg = suc ? "获取成功" : "获取失败",
                tokenStr = jwtStr
            };
        }
        //用户使用手机号登录





        /// <summary>
        /// 获取所有用户列表
        /// </summary>
        /// <param name="page"></param>
        /// <param name="key"></param>
        /// <param name="intPageSize"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<MessageModel<PageModel<PatientUser>>> Get(int page = 1, string key = "", int intPageSize = 50)
        {
            if (string.IsNullOrEmpty(key) || string.IsNullOrWhiteSpace(key))
            {
                key = "";
            }

            Expression<Func<PatientUser, bool>> whereExpression = a => true;

            return new MessageModel<PageModel<PatientUser>>()
            {
                msg = "获取成功",
                success = true,
                response = await _patientUserServices.QueryPage(whereExpression, page, intPageSize)
            };

        }
        /// <summary>
        /// 根据Id查询数据
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        [HttpGet("{id}")]
        public async Task<MessageModel<PatientUser>> Get(string id)
        {
            return new MessageModel<PatientUser>()
            {
                msg = "获取成功",
                success = true,
                response = await _patientUserServices.QueryById(id)
            };
        }
        //    /// <summary>
        //    /// 添加用户
        //    /// </summary>
        //    /// <param name="request"></param>
        //    /// <returns></returns>
        //    [HttpPost]
        //    public async Task<MessageModel<string>> Post([FromBody] PatientUser request)
        //    {
        //        var data = new MessageModel<string>();

        //        var id = await _patientUserServices.Add(request);
        //        data.success = id > 0;
        //        if (data.success)
        //        {
        //            data.response = id.ObjToString();
        //            data.msg = "添加成功";
        //        }

        //        return data;
        //    }

        //    [HttpPut]
        //    public async Task<MessageModel<string>> Put([FromBody] PatientUser request)
        //    {
        //        var data = new MessageModel<string>();
        //        data.success = await _patientUserServices.Update(request);
        //        if (data.success)
        //        {
        //            data.msg = "更新成功";
        //            data.response = request?.PatientUserId.ObjToString();
        //        }

        //        return data;
        //    }

        //    [HttpDelete]
        //    public async Task<MessageModel<string>> Delete(int id)
        //    {
        //        var data = new MessageModel<string>();
        //        var model = await _patientUserServices.QueryById(id);
        //        model.IsDeleted = true;
        //        data.success = await _patientUserServices.Update(model);
        //        if (data.success)
        //        {
        //            data.msg = "删除成功";
        //            data.response = model?.PatientUserId.ObjToString();
        //        }

        //        return data;
        //    }
    }
    public class LoginUserInfo
    {
        public string Login_name { get; set; }
        public string User_img { get; set; }
    }
}